package net.bac.sbe.web.sonar.server.dev.utils.xml;
import java.io.File;
import java.io.InputStream;
import java.io.StringReader;
import java.io.StringWriter;

import javax.xml.bind.JAXB;
import javax.xml.bind.JAXBContext;
import javax.xml.bind.JAXBException;
import javax.xml.bind.Marshaller;

/**
 * <b>REVISION 1.0</b>
 * <br>
 * <b>Fecha:</b> 14-06-2013
 * <br>
 * <b>Bac Payments (Paguelo2)</b>
 * <p>Clase util para la representación de objetos a xml y viseversa</p>
 *
 * @autor jgamboa-Centauro Solutions(1.0)
 * @version 1.0
 */
public final class XmlBinding {

	private static final String XML_HEAD =  "<?xml version='1.0' encoding='ISO-8859-1'?>";//$NON-NLS-1$

	/**
	 * Constructor default
	 */
	private XmlBinding(){
	}

	/**
	 * Retorna una instancia de clase
	 * @return
	 */
	public static XmlBinding getInstance(){
		return new XmlBinding();
	}
	/**
	 * Parsea un string que contiene una estructura xml a un objeto específico
	 * @param xml - Estructura xml a parsear
	 * @param type - Clase del objeto
	 * @return <code><T></code> Tipo de Clase a retornar
	 * @throws DataBindingException
	 */
	public static <T> T xmlToObject(String xml, Class<T> type) {
		return JAXB.unmarshal(new StringReader(xml), type);
	}

	/**
	 * Parsea un archivo xml a un objeto específico
	 * @param filePath - Ruta del archivo
	 * @param type - Tipo de clase
	 * @return <code><T></code> Tipo de Clase a retornar
	 * @throws DataBindingException
	 */
	public static <T> T xmlFileToObject(String filePath, Class<T> type) {
		return JAXB.unmarshal(new File (filePath), type);
	}

	/**
	 * Parsea un archivo xml a un objeto específico
	 * @param filePath - Ruta del archivo
	 * @param type - Tipo de clase
	 * @return <code><T></code> Tipo de Clase a retornar
	 * @throws DataBindingException
	 */
	public static <T> T xmlResourceToObject(InputStream filePath, Class<T> type) {
		return JAXB.unmarshal(filePath, type);
	}

	/**
	 * Genera un xml apartir de un objeto cargado
	 * @param obClass - Objeto a generar
	 * @return <code>String</code> - Xml generado
	 * @throws JAXBException
	 */
	public static String objectToXml(Object obClass) throws JAXBException {
		StringBuilder stringBuilder = null;
		StringWriter writer = null;
		JAXBContext context = null;
		Marshaller marshaller = null;
		int size = 0;

		writer = new StringWriter();
		context = JAXBContext.newInstance(obClass.getClass());
		marshaller = context.createMarshaller();
		marshaller.setProperty(Marshaller.JAXB_FRAGMENT, true);
		marshaller.marshal(obClass, writer);

		size = XML_HEAD.length() + writer.toString().length();
		stringBuilder = new StringBuilder(size);
		stringBuilder.append(XML_HEAD);
		stringBuilder.append(writer.toString());


		return stringBuilder.toString();
	}
}
